package mt521.cam.ac.uk;

import java.io.ByteArrayOutputStream;

public class Dolphin {
    
    private static double backgroundLevel = 0.0;
    private static int chunkSize = Encode.getChunkSize();

    public static void main(String[] args) {
        ByteArrayOutputStream stream = new ByteArrayOutputStream();
        double[] dTone = new double[chunkSize];
        double[] transformed = new double[chunkSize];
        long lFreq;
        byte bFreq;
        byte[] bTone = FileOperators.mic(128);   //number of bytes to read is random at this stage
        System.out.println("Sound Captured.");
        backgroundLevel = getBackground(bTone);
        
        for(int i=chunkSize; i<bTone.length; i+=chunkSize) {    //first 512 used in comparison, required to never be data
            for(int j = 0; j<chunkSize; j++) {
                dTone[j] = (double) bTone[i+j];
            }
            transformed = Decode.fft(dTone);
            if (isData(transformed)){
                lFreq = (Decode.getFrequency(transformed)-300)/30;
                bFreq = lFreq>127 ? (byte) (lFreq-256) : (byte) lFreq;
                stream.write(bFreq);
            }
        }
        System.out.println("Sound Decoded.");
        byte[] result = stream.toByteArray();
        FileOperators.convertToFile(result,"dolphin");
        System.out.println("New file saved to dolphin.txt");
    }
    
    public static double getBackground(byte[] bTone) {
        double max = 0.0;
        double[] dTone = new double[chunkSize];
        for(int j = 0; j<chunkSize; j++) {
            dTone[j] = (double) bTone[j];
        }
        double[] transformed = Decode.fft(dTone);       //is half the size as second half ignored
        for (int i=0; i<transformed.length; i++) {
            max = transformed[i]>max ? transformed[i] : max;
        }
        return max*1.2;      //allow a small tolerance, up to one fifth higher than the sample.
    }
    
    public static boolean isData(double[] amp) {
        double max = 0.0;
        for (int i=0; i<amp.length; i++) {
            max = amp[i]>max ? amp[i] : max;
        }
        if (max>backgroundLevel) {
            return true;
        }
        else {
            return false;
        }
    }
}